source: ProjectBuilder/devel/pb/bin/pb@ 417

Last change on this file since 417 was 417, checked in by Bruno Cornec, 16 years ago
  • Reintegrates $pbproj as variable for filter functions (needed for PBPROJ expansion)
  • Fix pbinit using perl functions support
  • Adds a virtual pbinit action support in pb_env_init
  • Property svn:executable set to *
File size: 51.6 KB
RevLine 
[5]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
[22]10# Syntax: see at end
[9]11
[18]12use strict 'vars';
[331]13use Getopt::Long qw(:config auto_abbrev no_ignore_case);
[9]14use Data::Dumper;
15use English;
[16]16use File::Basename;
[26]17use File::Copy;
[395]18use File::stat;
19use File::Temp qw(tempdir);
[13]20use POSIX qw(strftime);
[17]21use lib qw (lib);
[329]22use ProjectBuilder::Version;
[318]23use ProjectBuilder::Base;
[405]24use ProjectBuilder::Conf;
25use ProjectBuilder::Distribution;
26use ProjectBuilder::CMS;
[416]27use ProjectBuilder::Env;
[405]28use ProjectBuilder::Filter;
[5]29
[397]30# Global variables
[5]31my %opts; # CLI Options
[9]32my $action; # action to realize
[320]33my $test = "FALSE"; # Not used
34my $force = 0; # Force VE/VM rebuild
35my $option = ""; # Not used
36my @pkgs; # list of packages
[95]37my $pbtag; # Global Tag variable
38my $pbver; # Global Version variable
[141]39my $pbscript; # Name of the script
[77]40my %pbver; # per package
41my %pbtag; # per package
[53]42my $pbrev; # Global REVISION variable
[152]43my $pbaccount; # Login to use to connect to the VM
[162]44my $pbport; # Port to use to connect to the VM
[199]45my $newver; # New version to create
[331]46my $iso; # ISO image for the VM to create
[5]47
[320]48my @date = pb_get_date();
49my $pbdate = strftime("%Y-%m-%d", @date);
[5]50
[331]51=pod
52
53=head1 NAME
54
55pb, aka project-builder.org - builds packages for your projects
56
57=head1 DESCRIPTION
58
59pb helps you build various packages directly from your project sources.
60Those sources could be handled by a CMS (Configuration Management System)
61such as Subversion, CVS, ... or being a simple reference to a compressed tar file.
62It's based on a set of configuration files, a set of provided macros to help
63you keeping build files as generic as possible. For example, a single .spec
64file should be required to generate for all rpm based distributions, even
65if you could also have multiple .spec files if required.
66
67=head1 SYNOPSIS
68
[332]69pb [-vhq][-r pbroot][-p project][[-s script -a account -P port][-m mach-1[,...]]][-i iso] <action> [<pkg1> ...]
[331]70
[332]71pb [--verbose][--help][--man][--quiet][--revision pbroot][--project project][[--script script --account account --port port][--machine mach-1[,...]]][--iso iso] <action> [<pkg1> ...]
[331]72
73=head1 OPTIONS
74
75=over 4
76
77=item B<-v|--verbose>
78
79Print a brief help message and exits.
80
81=item B<-q|--quiet>
82
83Do not print any output.
84
85=item B<-h|--help>
86
87Print a brief help message and exits.
88
89=item B<--man>
90
91Prints the manual page and exits.
92
93=item B<-m|--machine machine1[,machine2,...]>
94
95Name of the Virtual Machines (VM) or Virtual Environments (VE) you want to build on (coma separated).
96All if none precised (or use the env variable PBV).
97
98=item B<-s|--script script>
99
100Name of the script you want to execute on the related VMs or VEs.
101
102=item B<-i|--iso iso_image>
103
104Name of the ISO image of the distribution you want to install on the related VMs.
105
106=item B<-a|--account account>
107
108Name of the account to use to connect on the related VMs.
109
110=item B<-P|--port port_number>
111
112Port number to use to connect on the related VMs.\n";
113
114=item B<-p|--project project_name>
115
116Name of the project you're working on (or use the env variable PBPROJ)
117
118=item B<-r|--revision revision>
119
120Path Name of the project revision under the CMS (or use the env variable PBROOT)
121
122=item B<-V|--version new_version>
123
124New version of the project to create based on the current one.
125
126=back
127
128=head1 ARGUMENTS
129
130<action> can be:
131
132=over 4
133
134=item B<cms2build>
135
136Create tar files for the project under your CMS.
137CMS supported are SVN and CVS
138parameters are packages to build
139if not using default list
140
141=item B<build2pkg>
142
143Create packages for your running distribution
144
145=item B<cms2pkg>
146
147cms2build + build2pkg
148
149=item B<build2ssh>
150
151Send the tar files to a SSH host
152
153=item B<cms2ssh>
154
155cms2build + build2ssh
156
157=item B<pkg2ssh>
158
159Send the packages built to a SSH host
160
161=item B<build2vm>
162
163Create packages in VMs, launching them if needed
164and send those packages to a SSH host once built
165VM type supported are QEMU
166
167=item B<build2ve>
168
169Create packages in VEs, creating it if needed
170and send those packages to a SSH host once built
171
172=item B<cms2vm>
173
174cms2build + build2vm
175
176=item B<cms2ve>
177
178cms2build + build2ve
179
180=item B<launchvm>
181
182Launch one virtual machine
183
184=item B<launchve>
185
186Launch one virtual environment
187
188=item B<script2vm>
189
190Launch one virtual machine if needed
191and executes a script on it
192
193=item B<script2ve>
194
195Execute a script in a virtual environment
196
197=item B<newvm>
198
199Create a new virtual machine
200
201=item B<newve>
202
203Create a new virtual environment
204
[346]205=item B<setupvm>
206
207Setup a virtual machine for pb usage
208
209=item B<setupve>
210
211Setup a virtual environment for pb usage
212
[331]213=item B<newver>
214
215Create a new version of the project derived
216from the current one
217
218=item B<newproj>
219
220Create a new project and a template set of
221configuration files under pbconf
222
223=back
224
225<pkgs> can be a list of packages, the keyword 'all' or nothing, in which case the default list of packages is taken (corresponding to the defpkgdir list of arguments in the configuration file).
226
227=head1 WEB SITES
228
229The main Web site of the project is available at L<http://www.project-builder.org/>. Bug reports should be filled using the trac instance of the project at L<http://trac.project-builder.org/>.
230
231=head1 USER MAILING LIST
232
233None exists for the moment.
234
235=head1 CONFIGURATION FILES
236
237Each pb user may have a configuration in F<$HOME/.pbrc>. The values in this file may overwrite any other configuration file value.
238
239Here is an example of such a configuration file:
240
241 #
242 # Define for each project the URL of its pbconf repository
243 # No default option allowed here as they need to be all different
244 #
245 # URL of the pbconf content
246 # This is the format of a classical URL with the extension of additional schema such as
247 # svn+ssh, cvs+ssh, ...
248 #
249 pbconfurl linuxcoe = cvs+ssh://:ext:bcornec@linuxcoe.cvs.sourceforge.net:/cvsroot/linuxcoe/pbconf
250
251 # This is normaly defined in the project's configuration file
252 # Url of the project
253 #
254 pburl linuxcoe = cvs+ssh://:ext:bcornec@linuxcoe.cvs.sourceforge.net:/cvsroot/linuxcoe
255
256 # All these URLs needs to be defined here as the are the entry point
257 # for how to build packages for the project
258 #
259 pbconfurl pb = svn+ssh://svn.project-builder.org/mondo/svn/pb/pbconf
260 pbconfurl mondorescue = svn+ssh://svn.project-builder.org/mondo/svn/project-builder/mondorescue/pbconf
261 pbconfurl collectl = svn+ssh://bruno@svn.mondorescue.org/mondo/svn/project-builder/collectl/pbconf
262 pbconfurl netperf = svn+ssh://svn.mondorescue.org/mondo/svn/project-builder/netperf/pbconf
263
264 # Under that dir will take place everything related to pb
265 # If you want to use VMs/chroot/..., then use $ENV{'HOME'} to make it portable
266 # to your VMs/chroot/...
267 # if not defined then /var/cache
268 pbdefdir default = $ENV{'HOME'}/project-builder
269 pbdefdir pb = $ENV{'HOME'}
270 pbdefdir linuxcoe = $ENV{'HOME'}/LinuxCOE/cvs
271 pbdefdir mondorescue = $ENV{'HOME'}/mondo/svn
272
273 # pbconfdir points to the directory where the CMS content of the pbconfurl is checked out
274 # If not defined, pbconfdir is under pbdefdir/pbproj/pbconf
275 pbconfdir linuxcoe = $ENV{'HOME'}/LinuxCOE/cvs/pbconf
276 pbconfdir mondorescue = $ENV{'HOME'}/mondo/svn/pbconf
277
278 # pbdir points to the directory where the CMS content of the pburl is checked out
279 # If not defined, pbdir is under pbdefdir/pbproj
280 # Only defined if we have access to the dev of the project
281 pbdir linuxcoe = $ENV{'HOME'}/LinuxCOE/cvs
282 pbdir mondorescue = $ENV{'HOME'}/mondo/svn
283
284 # -daemonize doesn't work with qemu 0.8.2
285 vmopt default = -m 384
286
287=head1 AUTHORS
288
289The Project-Builder.org team L<http://trac.project-builder.org/> lead by Bruno Cornec L<mailto:bruno@project-builder.org>.
290
291=head1 COPYRIGHT
292
293Project-Builder.org is distributed under the GPL v2.0 license
294described in the file C<COPYING> included with the distribution.
295
296=cut
297
298# ---------------------------------------------------------------------------
299
300# Old syntax
301#getopts('a:fhi:l:m:P:p:qr:s:vV:',\%opts);
302
[75]303my ($projectbuilderver,$projectbuilderrev) = pb_version_init();
[331]304
[397]305# Initialize the syntax string
306
307pb_syntax_init("pb (aka project-builder.org) Version $projectbuilderver-$projectbuilderrev\n");
308
[331]309GetOptions("help|?|h" => \$opts{'h'},
310 "man" => \$opts{'man'},
311 "verbose|v+" => \$opts{'v'},
312 "quiet|q" => \$opts{'q'},
313 "log-files|l=s" => \$opts{'l'},
314 "force|f" => \$opts{'f'},
315 "account|a=s" => \$opts{'a'},
316 "revision|r=s" => \$opts{'r'},
317 "script|s=s" => \$opts{'s'},
318 "machines|mock|m=s" => \$opts{'m'},
319 "port|P=i" => \$opts{'P'},
320 "project|p=s" => \$opts{'p'},
321 "iso|i=s" => \$opts{'i'},
322 "version|V=s" => \$opts{'V'},
323) || pb_syntax(-1,0);
324
[21]325if (defined $opts{'h'}) {
[331]326 pb_syntax(0,1);
[21]327}
[331]328if (defined $opts{'man'}) {
329 pb_syntax(0,2);
330}
[21]331if (defined $opts{'v'}) {
[331]332 $debug = $opts{'v'};
[318]333 pb_log(0,"Debug value: $debug\n");
[21]334}
[320]335if (defined $opts{'f'}) {
336 $force=1;
337}
[21]338if (defined $opts{'q'}) {
339 $debug=-1;
340}
[22]341if (defined $opts{'l'}) {
342 open(LOG,"> $opts{'l'}") || die "Unable to log to $opts{'l'}: $!";
[348]343 $LOG = \*LOG;
[22]344 $debug = 0 if ($debug == -1);
345 }
[315]346pb_log_init($debug, $LOG);
347
[67]348# Handle root of the project if defined
349if (defined $opts{'r'}) {
[340]350 $ENV{'PBROOTDIR'} = $opts{'r'};
[67]351}
[91]352# Handle virtual machines if any
353if (defined $opts{'m'}) {
[320]354 $ENV{'PBV'} = $opts{'m'};
[91]355}
[141]356if (defined $opts{'s'}) {
357 $pbscript = $opts{'s'};
358}
[152]359if (defined $opts{'a'}) {
360 $pbaccount = $opts{'a'};
[347]361 die "option -a requires a -s script option" if (not defined $pbscript);
[152]362}
[162]363if (defined $opts{'P'}) {
364 $pbport = $opts{'P'};
365}
[199]366if (defined $opts{'V'}) {
367 $newver = $opts{'V'};
368}
[262]369if (defined $opts{'i'}) {
370 $iso = $opts{'i'};
371}
[108]372
373# Get Action
374$action = shift @ARGV;
[331]375die pb_syntax(-1,1) if (not defined $action);
[108]376
[314]377my ($filteredfiles, $supfiles, $defpkgdir, $extpkgdir);
[273]378my $pbinit = undef;
379$pbinit = 1 if ($action =~ /^newproj$/);
[108]380
[59]381# Handles project name if any
[108]382# And get global params
[353]383($filteredfiles, $supfiles, $defpkgdir, $extpkgdir) = pb_env_init($opts{'p'},$pbinit,$action);
[59]384
[315]385pb_log(0,"Project: $ENV{'PBPROJ'}\n");
386pb_log(0,"Action: $action\n");
[9]387
388# Act depending on action
389if ($action =~ /^cms2build$/) {
[77]390 pb_cms2build();
391} elsif ($action =~ /^build2pkg$/) {
392 pb_build2pkg();
393} elsif ($action =~ /^cms2pkg$/) {
394 pb_cms2build();
395 pb_build2pkg();
[88]396} elsif ($action =~ /^build2ssh$/) {
397 pb_build2ssh();
[220]398} elsif ($action =~ /^cms2ssh$/) {
399 pb_cms2build();
400 pb_build2ssh();
[88]401} elsif ($action =~ /^pkg2ssh$/) {
402 pb_pkg2ssh();
[320]403} elsif ($action =~ /^build2ve$/) {
404 pb_build2v("ve");
[91]405} elsif ($action =~ /^build2vm$/) {
[320]406 pb_build2v("vm");
407} elsif ($action =~ /^cms2ve$/) {
408 pb_cms2build();
409 pb_build2v("ve");
[91]410} elsif ($action =~ /^cms2vm$/) {
411 pb_cms2build();
[320]412 pb_build2v("vm");
[141]413} elsif ($action =~ /^launchvm$/) {
[320]414 pb_launchv("vm",$ENV{'PBV'},0);
415} elsif ($action =~ /^launchve$/) {
416 pb_launchv("ve",$ENV{'PBV'},0);
[142]417} elsif ($action =~ /^script2vm$/) {
[320]418 pb_script2v($pbscript,"vm");
419} elsif ($action =~ /^script2ve$/) {
420 pb_script2v($pbscript,"ve");
[199]421} elsif ($action =~ /^newver$/) {
422 pb_newver();
[320]423} elsif ($action =~ /^newve$/) {
424 pb_launchv("ve",$ENV{'PBV'},1);
[262]425} elsif ($action =~ /^newvm$/) {
[320]426 pb_launchv("vm",$ENV{'PBV'},1);
[346]427} elsif ($action =~ /^setupve$/) {
[353]428 pb_setup_v("ve");
[346]429} elsif ($action =~ /^setupvm$/) {
[353]430 pb_setup_v("vm");
[273]431} elsif ($action =~ /^newproj$/) {
432 # Nothing to do - already done in pb_env_init
[106]433} elsif ($action =~ /^clean$/) {
[77]434} else {
[315]435 pb_log(0,"\'$action\' is not available\n");
[331]436 pb_syntax(-2,1);
[77]437}
438
439sub pb_cms2build {
440
[357]441 my $pkg = pb_cms_get_pkg($defpkgdir,$extpkgdir);
442 my @pkgs = @$pkg;
443 my %pkgs;
[9]444
[341]445 my ($scheme, $uri) = pb_cms_init($pbinit);
[331]446
[313]447 my ($pkgv, $pkgt) = pb_conf_get_if("pkgver","pkgtag");
[174]448
449 # declare packager for filtering
[320]450 my ($tmp) = pb_conf_get("pbpackager");
[353]451 $ENV{'PBPACKAGER'} = $tmp->{$ENV{'PBPROJ'}};
[174]452
[27]453 foreach my $pbpkg (@pkgs) {
[115]454 $ENV{'PBPKG'} = $pbpkg;
[98]455 if ((defined $pkgv) && (defined $pkgv->{$pbpkg})) {
456 $pbver = $pkgv->{$pbpkg};
[9]457 } else {
[353]458 $pbver = $ENV{'PBPROJVER'};
[9]459 }
[98]460 if ((defined $pkgt) && (defined $pkgt->{$pbpkg})) {
461 $pbtag = $pkgt->{$pbpkg};
[9]462 } else {
[353]463 $pbtag = $ENV{'PBPROJTAG'};
[9]464 }
[95]465
[16]466 $pbrev = $ENV{'PBREVISION'};
[319]467 pb_log(0,"\n");
468 pb_log(0,"Management of $pbpkg $pbver-$pbtag (rev $pbrev)\n");
[9]469 die "Unable to get env var PBDESTDIR" if (not defined $ENV{'PBDESTDIR'});
[16]470 # Clean up dest if necessary. The export will recreate it
[27]471 my $dest = "$ENV{'PBDESTDIR'}/$pbpkg-$pbver";
[74]472 pb_rm_rf($dest) if (-d $dest);
[9]473
474 # Export CMS tree for the concerned package to dest
475 # And generate some additional files
476 $OUTPUT_AUTOFLUSH=1;
[29]477
[9]478 # computes in which dir we have to work
[113]479 my $dir = $defpkgdir->{$pbpkg};
480 $dir = $extpkgdir->{$pbpkg} if (not defined $dir);
[315]481 pb_log(2,"def:".Dumper($defpkgdir)." ext: ".Dumper($extpkgdir)." \n");
[9]482
[340]483 # Exporting from CMS
484 pb_cms_export($uri,"$ENV{'PBDIR'}/$dir",$dest);
[315]485
[285]486 # Get project info on authors and log file
[340]487 my $chglog = "$ENV{'PBROOTDIR'}/$pbpkg/pbcl";
488 $chglog = "$ENV{'PBROOTDIR'}/pbcl" if (! -f $chglog);
[285]489 $chglog = undef if (! -f $chglog);
490
[340]491 my $authors = "$ENV{'PBROOTDIR'}/$pbpkg/pbauthors";
492 $authors = "$ENV{'PBROOTDIR'}/pbauthors" if (! -f $authors);
[285]493 $authors = "/dev/null" if (! -f $authors);
494
[9]495 # Extract cms log history and store it
[285]496 if ((defined $chglog) && (! -f "$dest/NEWS")) {
[315]497 pb_log(2,"Generating NEWS file from $chglog\n");
[285]498 copy($chglog,"$dest/NEWS") || die "Unable to create $dest/NEWS";
499 }
[340]500 pb_cms_log($scheme,"$ENV{'PBDIR'}/$dir",$dest,$chglog,$authors);
[29]501
[21]502 my %build;
[91]503
[328]504 my @pt;
505 @pt = pb_conf_get_if("vmlist","velist");
[340]506 my $tmpl = "";
507 if (defined $pt[0]->{$ENV{'PBPROJ'}}) {
508 $tmpl .= $pt[0]->{$ENV{'PBPROJ'}};
509 }
510 if (defined $pt[1]->{$ENV{'PBPROJ'}}) {
511 # the 2 lists needs to be grouped with a ',' separated them
512 if ($tmpl ne "") {
513 $tmpl .= ",";
514 }
515 $tmpl .= $pt[1]->{$ENV{'PBPROJ'}}
516 }
517 foreach my $d (split(/,/,$tmpl)) {
[315]518 my ($name,$ver,$arch) = split(/-/,$d);
519 chomp($arch);
[99]520 my ($ddir, $dver, $dfam, $dtype, $pbsuf) = pb_distro_init($name,$ver);
[315]521 pb_log(2,"DEBUG: distro tuple: ".Dumper($ddir, $dver, $dfam, $dtype, $pbsuf)."\n");
522 pb_log(2,"DEBUG Filtering PBDATE => $pbdate, PBTAG => $pbtag, PBVER => $pbver\n");
[13]523
[16]524 # Filter build files from the less precise up to the most with overloading
[13]525 # Filter all files found, keeping the name, and generating in dest
[16]526
[340]527 # Find all build files first relatively to PBROOTDIR
[300]528 # Find also all specific files referenced in the .pb conf file
[320]529 my %bfiles = ();
530 my %pkgfiles = ();
[21]531 $build{"$ddir-$dver"} = "yes";
[315]532
[340]533 if (-d "$ENV{'PBROOTDIR'}/$pbpkg/$dtype") {
534 pb_list_bfiles("$ENV{'PBROOTDIR'}/$pbpkg/$dtype",$pbpkg,\%bfiles,\%pkgfiles,$supfiles);
535 } elsif (-d "$ENV{'PBROOTDIR'}/$pbpkg/$dfam") {
536 pb_list_bfiles("$ENV{'PBROOTDIR'}/$pbpkg/$dfam",$pbpkg,\%bfiles,\%pkgfiles,$supfiles);
537 } elsif (-d "$ENV{'PBROOTDIR'}/$pbpkg/$ddir") {
538 pb_list_bfiles("$ENV{'PBROOTDIR'}/$pbpkg/$ddir",$pbpkg,\%bfiles,\%pkgfiles,$supfiles);
539 } elsif (-d "$ENV{'PBROOTDIR'}/$pbpkg/$ddir-$dver") {
540 pb_list_bfiles("$ENV{'PBROOTDIR'}/$pbpkg/$ddir-$dver",$pbpkg,\%bfiles,\%pkgfiles,$supfiles);
[13]541 } else {
[21]542 $build{"$ddir-$dver"} = "no";
[13]543 next;
544 }
[315]545 pb_log(2,"DEBUG bfiles: ".Dumper(\%bfiles)."\n");
[13]546
[15]547 # Get all filters to apply
[77]548 my $ptr = pb_get_filters($pbpkg, $dtype, $dfam, $ddir, $dver);
[15]549
[19]550 # Apply now all the filters on all the files concerned
551 # destination dir depends on the type of file
552 if (defined $ptr) {
[300]553 foreach my $f (values %bfiles,values %pkgfiles) {
[417]554 pb_filter_file_pb("$ENV{'PBROOTDIR'}/$f",$ptr,"$dest/pbconf/$ddir-$dver/".basename($f),$dtype,$pbsuf,$pbpkg,$pbver,$pbtag,$pbrev,$pbdate,$defpkgdir,$extpkgdir,$ENV{'PBPACKAGER'},$chglog,$ENV{'PBPROJ'});
[16]555 }
[15]556 }
[18]557 }
[315]558 my @found;
559 my @notfound;
560 foreach my $b (keys %build) {
561 push @found,$b if ($build{$b} =~ /yes/);
562 push @notfound,$b if ($build{$b} =~ /no/);
[21]563 }
[315]564 pb_log(0,"Build files generated for ".join(',',@found)."\n");
565 pb_log(0,"No Build files found for ".join(',',@notfound)."\n") if (@notfound);
[236]566 # Get the generic filter (all.pbf) and
567 # apply those to the non-build files including those
568 # generated by pbinit if applicable
569
570 # Get only all.pbf filter
[357]571 my $ptr = pb_get_filters($pbpkg);
[236]572
573 my $liste ="";
574 if (defined $filteredfiles->{$pbpkg}) {
575 foreach my $f (split(/,/,$filteredfiles->{$pbpkg})) {
[417]576 pb_filter_file_inplace($ptr,"$dest/$f",$pbpkg,$pbver,$pbtag,$pbrev,$pbdate,$ENV{'PBPACKAGER'},$ENV{'PBPROJ'});
[238]577 $liste = "$f $liste";
[236]578 }
579 }
[315]580 pb_log(2,"Files ".$liste."have been filtered\n");
[236]581
[265]582 # Prepare the dest directory for archive
[340]583 if (-x "$ENV{'PBROOTDIR'}/$pbpkg/pbinit") {
[417]584 pb_filter_file("$ENV{'PBROOTDIR'}/$pbpkg/pbinit",$ptr,"$ENV{'PBTMP'}/pbinit",$pbpkg,$pbver,$pbtag,$pbrev,$pbdate,$ENV{'PBPACKAGER'},$ENV{'PBPROJ'});
[266]585 chmod 0755,"$ENV{'PBTMP'}/pbinit";
[340]586 pb_system("cd $dest ; $ENV{'PBTMP'}/pbinit","Executing init script from $ENV{'PBROOTDIR'}/$pbpkg/pbinit");
[265]587 }
588
[18]589 # Archive dest dir
[69]590 chdir "$ENV{'PBDESTDIR'}" || die "Unable to change dir to $ENV{'PBDESTDIR'}";
[25]591 # Possibility to look at PBSRC to guess more the filename
[94]592 pb_system("tar cfz $pbpkg-$pbver.tar.gz $pbpkg-$pbver","Creating $pbpkg tar files compressed");
[344]593 pb_log(0,"Under $ENV{'PBDESTDIR'}/$pbpkg-$pbver.tar.gz\n");
[83]594
[357]595 # Keep track of version-tag per pkg
596 $pkgs{$pbpkg} = "$pbver-$pbtag";
[83]597
[288]598 # Final cleanup
599 pb_rm_rf($dest) if (-d $dest);
[9]600 }
[357]601
602 # Keep track of per package version
603 pb_log(2,"DEBUG pkgs: ".Dumper(%pkgs)."\n");
604 open(PKG,"> $ENV{'PBDESTDIR'}/$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}.pb") || die "Unable to create $ENV{'PBDESTDIR'}/$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}.pb";
605 foreach my $pbpkg (@pkgs) {
606 print PKG "pbpkg $pbpkg = $pkgs{$pbpkg}\n";
607 }
608 close(PKG);
609
610 # Keep track of what is generated by default
611 # We need to store the dir and info on version-tag
612 # Base our content on the existing .pb file
613 copy("$ENV{'PBROOTDIR'}/$ENV{'PBPROJ'}.pb","$ENV{'PBDESTDIR'}/pbrc");
614 open(LAST,">> $ENV{'PBDESTDIR'}/pbrc") || die "Unable to create $ENV{'PBDESTDIR'}/pbrc";
615 print LAST "pbroot $ENV{'PBPROJ'} = $ENV{'PBROOTDIR'}\n";
616 print LAST "pbprojver $ENV{'PBPROJ'} = $ENV{'PBPROJVER'}\n";
617 print LAST "pbprojtag $ENV{'PBPROJ'} = $ENV{'PBPROJTAG'}\n";
618 print LAST "pbpackager $ENV{'PBPROJ'} = $ENV{'PBPACKAGER'}\n";
619 close(LAST);
[77]620}
[22]621
[77]622sub pb_build2pkg {
623
[22]624 # Get the running distro to build on
[99]625 my ($ddir, $dver, $dfam, $dtype, $pbsuf) = pb_distro_init();
[315]626 pb_log(2,"DEBUG: distro tuple: ".join(',',($ddir, $dver, $dfam, $dtype, $pbsuf))."\n");
[22]627
[353]628 # Get list of packages to build
[83]629 # Get content saved in cms2build
[353]630 my $ptr = pb_get_pkg();
631 @pkgs = @$ptr;
632
633 my ($pkg) = pb_conf_read("$ENV{'PBDESTDIR'}/$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}.pb","pbpkg");
[83]634 $pkg = { } if (not defined $pkg);
635
[25]636 chdir "$ENV{'PBBUILDDIR'}";
[126]637 my $made = ""; # pkgs made during build
[27]638 foreach my $pbpkg (@pkgs) {
[88]639 my $vertag = $pkg->{$pbpkg};
[77]640 # get the version of the current package - maybe different
641 ($pbver,$pbtag) = split(/-/,$vertag);
642
[27]643 my $src="$ENV{'PBDESTDIR'}/$pbpkg-$pbver.tar.gz";
[315]644 pb_log(2,"Source file: $src\n");
[25]645
[315]646 pb_log(2,"Working directory: $ENV{'PBBUILDDIR'}\n");
[25]647 if ($dtype eq "rpm") {
648 foreach my $d ('RPMS','SRPMS','SPECS','SOURCES','BUILD') {
[28]649 if (! -d "$ENV{'PBBUILDDIR'}/$d") {
[96]650 pb_mkdir_p("$ENV{'PBBUILDDIR'}/$d") || die "Please ensure that you can write into $ENV{'PBBUILDDIR'} to create $d\nchown the $ENV{'PBBUILDDIR'} directory to your uid";
[28]651 }
[25]652 }
653
[315]654 # Remove in case a previous link/file was there
[301]655 unlink "$ENV{'PBBUILDDIR'}/SOURCES/".basename($src);
[188]656 symlink "$src","$ENV{'PBBUILDDIR'}/SOURCES/".basename($src) || die "Unable to symlink $src in $ENV{'PBBUILDDIR'}/SOURCES";
[25]657 # We need to first extract the spec file
[28]658 my @specfile;
[77]659 @specfile = pb_extract_build_files($src,"$pbpkg-$pbver/pbconf/$ddir-$dver/","$ENV{'PBBUILDDIR'}/SPECS");
[25]660
[315]661 pb_log(2,"specfile: ".Dumper(\@specfile)."\n");
[25]662 # set LANGUAGE to check for correct log messages
663 $ENV{'LANGUAGE'}="C";
[28]664 foreach my $f (@specfile) {
665 if ($f =~ /\.spec$/) {
[353]666 pb_system("rpmbuild --define \'packager $ENV{'PBPACKAGER'}\' --define \"_topdir $ENV{'PBBUILDDIR'}\" -ba $f","Building package with $f under $ENV{'PBBUILDDIR'}");
[28]667 last;
668 }
669 }
[136]670 $made="$made RPMS/*/$pbpkg-$pbver-$pbtag$pbsuf.*.rpm SRPMS/$pbpkg-$pbver-$pbtag$pbsuf.src.rpm";
[149]671 if (-f "/usr/bin/rpmlint") {
672 pb_system("rpmlint $made","Checking validity of rpms with rpmlint");
[150]673 }
[118]674 } elsif ($dtype eq "deb") {
[149]675 chdir "$ENV{'PBBUILDDIR'}" || die "Unable to chdir to $ENV{'PBBUILDDIR'}";
[274]676 pb_system("tar xfz $src","Extracting sources");
[149]677
678 chdir "$pbpkg-$pbver" || die "Unable to chdir to $pbpkg-$pbver";
[310]679 pb_rm_rf("debian");
[149]680 symlink "pbconf/$ddir-$dver","debian" || die "Unable to symlink to pbconf/$ddir-$dver";
[199]681 chmod 0755,"debian/rules";
[149]682 pb_system("dpkg-buildpackage -us -uc -rfakeroot","Building package");
[136]683 $made="$made $pbpkg"."_*.deb $pbpkg"."_*.dsc $pbpkg"."_*.tar.gz";
[315]684 if (-f "/usr/bin/lintian") {
685 pb_system("lintian $made","Checking validity of debs with lintian");
686 }
[87]687 } elsif ($dtype eq "ebuild") {
[149]688 my @ebuildfile;
689 # For gentoo we need to take pb as subsystem name
[295]690 # We put every apps here under sys-apps. hope it's correct
691 # We use pb's home dir in order o have a single OVERLAY line
692 my $tmpd = "$ENV{'HOME'}/portage/pb/sys-apps/$pbpkg";
693 pb_mkdir_p($tmpd) if (! -d "$tmpd");
694 pb_mkdir_p("$ENV{'HOME'}/portage/distfiles") if (! -d "$ENV{'HOME'}/portage/distfiles");
[149]695
[295]696 # We need to first extract the ebuild file
697 @ebuildfile = pb_extract_build_files($src,"$pbpkg-$pbver/pbconf/$ddir-$dver/","$tmpd");
[149]698
699 # Prepare the build env for gentoo
700 my $found = 0;
[295]701 my $pbbd = $ENV{'HOME'};
[150]702 $pbbd =~ s|/|\\/|g;
[295]703 if (-r "/etc/make.conf") {
704 open(MAKE,"/etc/make.conf");
705 while (<MAKE>) {
706 $found = 1 if (/$pbbd\/portage/);
707 }
708 close(MAKE);
[149]709 }
710 if ($found == 0) {
[295]711 pb_system("sudo sh -c 'echo PORTDIR_OVERLAY=\"$ENV{'HOME'}/portage\" >> /etc/make.conf'");
[149]712 }
[295]713 #$found = 0;
714 #if (-r "/etc/portage/package.keywords") {
715 #open(KEYW,"/etc/portage/package.keywords");
716 #while (<KEYW>) {
717 #$found = 1 if (/portage\/pb/);
718 #}
719 #close(KEYW);
720 #}
721 #if ($found == 0) {
722 #pb_system("sudo sh -c \"echo portage/pb >> /etc/portage/package.keywords\"");
723 #}
[149]724
725 # Build
726 foreach my $f (@ebuildfile) {
727 if ($f =~ /\.ebuild$/) {
[295]728 move($f,"$tmpd/$pbpkg-$pbver.ebuild");
729 pb_system("cd $tmpd ; ebuild $pbpkg-$pbver.ebuild clean ; ebuild $pbpkg-$pbver.ebuild digest ; ebuild $pbpkg-$pbver.ebuild package");
730 # Now move it where pb expects it
731 pb_mkdir_p("$ENV{'PBBUILDDIR'}/portage/pb/sys-apps/$pbpkg");
732 move("$tmpd/$pbpkg-$pbver.ebuild","$ENV{'PBBUILDDIR'}/portage/pb/sys-apps/$pbpkg");
[149]733 }
734 }
735
[295]736 $made="$made portage/pb/sys-apps/$pbpkg/$pbpkg-$pbver.ebuild";
[118]737 } elsif ($dtype eq "slackware") {
[136]738 $made="$made build-$pbpkg/$pbpkg-$pbver-*-$pbtag.tgz";
[118]739 pb_mkdir_p("$ENV{'PBBUILDDIR'}/install") if (! -d "$ENV{'PBBUILDDIR'}/install");
[87]740 } else {
[118]741 die "Unknown dtype format $dtype";
[87]742 }
743 }
[118]744 # Keep track of what is generated so that we can get them back from VMs
[353]745 open(KEEP,"> $ENV{'PBBUILDDIR'}/pbgen-$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}") || die "Unable to create $ENV{'PBBUILDDIR'}/pbgen-$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}";
[118]746 print KEEP "$made\n";
747 close(KEEP);
[87]748}
749
[88]750sub pb_build2ssh {
[320]751 pb_send2target("Sources");
[90]752}
[87]753
[90]754sub pb_pkg2ssh {
[320]755 pb_send2target("Packages");
[90]756}
757
[108]758# By default deliver to the the public site hosting the
[320]759# ftp structure (or whatever) or a VM/VE
760sub pb_send2target {
[90]761
762 my $cmt = shift;
[320]763 my $v = shift || undef;
[142]764 my $vmexist = shift || 0; # 0 is FALSE
[200]765 my $vmpid = shift || 0; # 0 is FALSE
[320]766
767 my $host = "sshhost";
768 my $login = "sshlogin";
769 my $dir = "sshdir";
770 my $port = "sshport";
771 my $conf = "sshconf";
772 my $rebuild = "sshrebuild";
[415]773 my $tmout = "vmtmout";
774 my $path = "vmpath";
[348]775 if (($cmt eq "vm") || ($cmt eq "Script")) {
[320]776 $login = "vmlogin";
[322]777 $dir = "pbdefdir";
[320]778 $tmout = "vmtmout";
779 $rebuild = "vmrebuild";
780 # Specific VM
781 $host = "vmhost";
782 $port = "vmport";
783 } elsif ($cmt eq "ve") {
784 $login = "velogin";
[322]785 $dir = "pbdefdir";
[320]786 $tmout = "vetmout";
787 # Specific VE
788 $path = "vepath";
789 $conf = "veconf";
790 $rebuild = "verebuild";
791 }
[158]792 my $cmd = "";
[90]793
[353]794 my $ptr = pb_get_pkg();
[87]795 @pkgs = @$ptr;
796
[136]797 # Get the running distro to consider
[347]798 my ($odir,$over,$oarch) = (undef, undef, undef);
[320]799 if (defined $v) {
800 ($odir,$over,$oarch) = split(/-/,$v);
[118]801 }
802 my ($ddir, $dver, $dfam, $dtype, $pbsuf) = pb_distro_init($odir,$over);
[315]803 pb_log(2,"DEBUG: distro tuple: ".join(',',($ddir, $dver, $dfam, $dtype, $pbsuf))."\n");
[87]804
[353]805 # Get list of packages to build
[87]806 # Get content saved in cms2build
[353]807 my ($pkg) = pb_conf_read("$ENV{'PBDESTDIR'}/$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}.pb","pbpkg");
[87]808 $pkg = { } if (not defined $pkg);
809
[118]810 my $src = "";
[87]811 chdir "$ENV{'PBBUILDDIR'}";
812 foreach my $pbpkg (@pkgs) {
[88]813 my $vertag = $pkg->{$pbpkg};
[87]814 # get the version of the current package - maybe different
815 ($pbver,$pbtag) = split(/-/,$vertag);
816
[320]817 if (($cmt eq "Sources") || ($cmt eq "vm") || ($cmt eq "ve")) {
[158]818 $src = "$src $ENV{'PBDESTDIR'}/$pbpkg-$pbver.tar.gz";
[166]819 if ($cmd eq "") {
820 $cmd = "ln -sf $pbpkg-$pbver.tar.gz $pbpkg-latest.tar.gz";
821 } else {
822 $cmd = "$cmd ; ln -sf $pbpkg-$pbver.tar.gz $pbpkg-latest.tar.gz";
823 }
[118]824 }
825 }
[417]826 # Adds conf file for availanility of conf elements
827 pb_conf_add("$ENV{'PBROOTDIR'}/$ENV{'PBPROJ'}.pb");
828
[320]829 if (($cmt eq "vm") || ($cmt eq "ve")) {
[353]830 $src="$src $ENV{'PBDESTDIR'}/pbscript $ENV{'PBROOTDIR'}/$ENV{'PBPROJ'}.pb $ENV{'PBDESTDIR'}/$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}.pb $ENV{'PBETC'} $ENV{'PBDESTDIR'}/pbrc";
[142]831 } elsif ($cmt eq "Script") {
832 $src="$src $ENV{'PBDESTDIR'}/pbscript";
[118]833 } elsif ($cmt eq "Packages") {
834 # Get package list from file made during build2pkg
[353]835 open(KEEP,"$ENV{'PBBUILDDIR'}/pbgen-$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}") || die "Unable to read $ENV{'PBBUILDDIR'}/pbgen-$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}";
[126]836 $src = <KEEP>;
[118]837 chomp($src);
838 close(KEEP);
839 if ($dtype eq "rpm") {
840 # Also make a pbscript to generate yum/urpmi bases
[108]841 # $src = "$src $ENV{'PBDESTDIR'}/pbscript"
[118]842 } elsif ($dtype eq "deb") {
843 # Also make a pbscript to generate apt bases
844 # $src = "$src $ENV{'PBDESTDIR'}/pbscript"
[90]845 }
[87]846 }
[320]847 # Remove potential leading spaces (cause problem with basename)
[132]848 $src =~ s/^ *//;
[129]849 my $basesrc = "";
[131]850 foreach my $i (split(/ +/,$src)) {
851 $basesrc .= " ".basename($i);
[130]852 }
[118]853
[320]854 pb_log(0,"Sources handled ($cmt): $src\n");
[355]855 pb_log(2,"values: ".Dumper(($host,$login,$dir,$port,$tmout,$rebuild,$path,$conf))."\n");
[415]856 my ($sshhost,$sshlogin,$sshdir,$sshport,$vtmout,$vepath) = pb_conf_get($host,$login,$dir,$port,$tmout,$path);
857 my ($vrebuild,$veconf) = pb_conf_get_if($rebuild,$conf);
[320]858 pb_log(2,"ssh: ".Dumper(($sshhost,$sshlogin,$sshdir,$sshport,$vtmout,$vrebuild,$vepath,$veconf))."\n");
859 # Not mandatory
860 my ($testver) = pb_conf_get_if("testver");
861
862 my $mac;
863 # Useless for VE
864 if ($cmt ne "ve") {
865 $mac = "$sshlogin->{$ENV{'PBPROJ'}}\@$sshhost->{$ENV{'PBPROJ'}}";
866 # Overwrite account value if passed as parameter
867 $mac = "$pbaccount\@$sshhost->{$ENV{'PBPROJ'}}" if (defined $pbaccount);
[355]868 pb_log(2, "DEBUG: pbaccount: $pbaccount => mac: $mac\n") if (defined $pbaccount);
[320]869 }
870
[108]871 my $tdir;
[136]872 my $bdir;
[142]873 if (($cmt eq "Sources") || ($cmt eq "Script")) {
[108]874 $tdir = "$sshdir->{$ENV{'PBPROJ'}}/src";
[320]875 } elsif (($cmt eq "vm") || ($cmt eq "ve")) {
876 $tdir = $sshdir->{$ENV{'PBPROJ'}}."/$ENV{'PBPROJ'}/delivery";
877 $bdir = $sshdir->{$ENV{'PBPROJ'}}."/$ENV{'PBPROJ'}/build";
[136]878 # Remove a potential $ENV{'HOME'} as bdir should be relative to pb's home
879 $bdir =~ s|\$ENV.+\}/||;
[90]880 } elsif ($cmt eq "Packages") {
[108]881 $tdir = "$sshdir->{$ENV{'PBPROJ'}}/$ddir/$dver";
[337]882 if ((defined $testver) && (defined $testver->{$ENV{'PBPROJ'}}) && ($testver->{$ENV{'PBPROJ'}} =~ /true/i)) {
[289]883 # This is a test pkg => target dir is under test
884 $tdir .= "/test";
[291]885 }
[90]886 } else {
887 return;
[22]888 }
[239]889
[320]890 # Useless for VE
891 my $nport;
892 if ($cmt ne "ve") {
893 $nport = $sshport->{$ENV{'PBPROJ'}};
894 $nport = "$pbport" if (defined $pbport);
895 }
896
[136]897 # Remove a potential $ENV{'HOME'} as tdir should be relative to pb's home
[132]898 $tdir =~ s|\$ENV.+\}/||;
899
[320]900 my $tm = $vtmout->{$ENV{'PBPROJ'}};
901
902 # ssh communication if not VE
[349]903 # should use a hash instead...
[320]904 my ($shcmd,$cpcmd,$cptarget,$cp2target);
905 if ($cmt ne "ve") {
[347]906 my $keyfile = pb_ssh_get(0);
907 $shcmd = "ssh -i $keyfile -q -p $nport $mac";
908 $cpcmd = "scp -i $keyfile -p -P $nport";
[320]909 $cptarget = "$mac:$tdir";
[351]910 if ($cmt eq "vm") {
911 $cp2target = "$mac:$bdir";
912 }
[320]913 } else {
914 my $tp = $vepath->{$ENV{'PBPROJ'}};
915 $shcmd = "sudo chroot $tp/$v /bin/su - $sshlogin->{$ENV{'PBPROJ'}} -c ";
916 $cpcmd = "cp -a ";
917 $cptarget = "$tp/$tdir";
918 $cp2target = "$tp/$bdir";
919 }
920
921 pb_system("$shcmd \"mkdir -p $tdir ; cd $tdir ; echo \'for i in $basesrc; do if [ -f \$i ]; then rm -f \$i; fi; done\ ; $cmd' | bash\"","Preparing $tdir on $cptarget");
922 pb_system("cd $ENV{'PBBUILDDIR'} ; $cpcmd $src $cptarget 2> /dev/null","$cmt delivery in $cptarget");
923 # For VE we need to change the owner manually - To be tested if needed
924 #if ($cmt eq "ve") {
925 #pb_system("cd $cptarget ; sudo chown -R $sshlogin->{$ENV{'PBPROJ'}} .","$cmt chown in $cptarget to $sshlogin->{$ENV{'PBPROJ'}}");
926 #}
927 pb_system("$shcmd \"echo \'cd $tdir ; if [ -f pbscript ]; then ./pbscript; fi\' | bash\"","Executing pbscript on $cptarget if needed");
928 if (($cmt eq "vm") || ($cmt eq "ve")) {
[128]929 # Get back info on pkg produced, compute their name and get them from the VM
[353]930 pb_system("$cpcmd $cp2target/pbgen-$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'} $ENV{'PBBUILDDIR'} 2> /dev/null","Get package names in $cp2target");
931 open(KEEP,"$ENV{'PBBUILDDIR'}/pbgen-$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}") || die "Unable to read $ENV{'PBBUILDDIR'}/pbgen-$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}";
[118]932 my $src = <KEEP>;
933 chomp($src);
934 close(KEEP);
[131]935 $src =~ s/^ *//;
[136]936 pb_mkdir_p("$ENV{'PBBUILDDIR'}/$odir/$over");
[320]937 # Change pgben to make the next send2target happy
[143]938 my $made = "";
[353]939 open(KEEP,"> $ENV{'PBBUILDDIR'}/pbgen-$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}") || die "Unable to write $ENV{'PBBUILDDIR'}/pbgen-$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}";
[136]940 foreach my $p (split(/ +/,$src)) {
[139]941 my $j = basename($p);
[320]942 pb_system("$cpcmd $cp2target/\'$p\' $ENV{'PBBUILDDIR'}/$odir/$over 2> /dev/null","Package recovery of $j in $cp2target");
[144]943 $made="$made $odir/$over/$j" if (($dtype ne "rpm") || ($j !~ /.src.rpm$/));
[136]944 }
[143]945 print KEEP "$made\n";
[139]946 close(KEEP);
[320]947 pb_system("$shcmd \"rm -rf $tdir $bdir\"","$cmt cleanup");
[355]948
949 # We want to send them to the ssh account so overwrite what has been done before
950 undef $pbaccount;
[357]951 pb_log(2,"Before sending pkgs, vmexist: $vmexist, vmpid: $vmpid\n");
[355]952 pb_send2target("Packages",$odir."-".$over."-".$oarch,$vmexist,$vmpid);
[320]953 if ((! $vmexist) && ($cmt eq "vm")) {
954 pb_system("$shcmd \"sudo /sbin/halt -p \"; sleep $tm ; echo \'if [ -d /proc/$vmpid ]; then kill -9 $vmpid; fi \' | bash ; sleep 10","VM $v halt (pid $vmpid)");
[142]955 }
[141]956 pb_rm_rf("$ENV{'PBBUILDDIR'}/$odir");
[108]957 }
[9]958}
[16]959
[320]960sub pb_script2v {
[142]961 my $pbscript=shift;
[320]962 my $vtype=shift;
[141]963
964 # Prepare the script to be executed on the VM
965 # in $ENV{'PBDESTDIR'}/pbscript
[142]966 if ((defined $pbscript ) && ($pbscript ne "$ENV{'PBDESTDIR'}/pbscript")) {
967 copy($pbscript,"$ENV{'PBDESTDIR'}/pbscript") || die "Unable to create $ENV{'PBDESTDIR'}/pbscript";
968 chmod 0755,"$ENV{'PBDESTDIR'}/pbscript";
969 }
[141]970
[320]971 my ($vm,$all) = pb_get_v($vtype);
972 my ($vmexist,$vmpid) = (undef,undef);
[142]973
[141]974 foreach my $v (@$vm) {
[320]975 # Launch the VM/VE
976 if ($vtype eq "vm") {
977 ($vmexist,$vmpid) = pb_launchv($vtype,$v,0);
[141]978
[320]979 # Skip that VM if something went wrong
980 next if (($vmpid == 0) && ($vmexist ==0));
981 }
[274]982
[142]983 # Gather all required files to send them to the VM
[320]984 # and launch the build through pbscript
985 pb_send2target("Script","$v",$vmexist,$vmpid);
[169]986
[142]987 }
988}
989
[320]990sub pb_launchv {
991 my $vtype = shift;
992 my $v = shift;
993 my $create = shift || 0; # By default do not create a VM
[310]994
[320]995 die "No VM/VE defined, unable to launch" if (not defined $v);
996 # Keep only the first VM in case many were given
997 $v =~ s/,.*//;
[310]998
[320]999 # Which is our local arch ? (standardize on i386 for those platforms)
1000 my $arch = `uname -m`;
1001 chomp($arch);
1002 $arch =~ s/i.86/i386/;
[310]1003
[320]1004 # Launch the VMs/VEs
1005 if ($vtype eq "vm") {
1006 die "-i iso parameter needed" if (((not defined $iso) || ($iso eq "")) && ($create != 0));
[310]1007
[415]1008 my ($ptr,$vmopt,$vmpath,$vmport,$vmtmout,$vmsize) = pb_conf_get("vmtype","vmopt","vmpath","vmport","vmtmout","vmsize");
[320]1009
1010 my $vmtype = $ptr->{$ENV{'PBPROJ'}};
1011 if (not defined $ENV{'PBVMOPT'}) {
1012 $ENV{'PBVMOPT'} = "";
[310]1013 }
[320]1014 if (defined $vmopt->{$ENV{'PBPROJ'}}) {
1015 $ENV{'PBVMOPT'} .= " $vmopt->{$ENV{'PBPROJ'}}" if ($ENV{'PBVMOPT'} !~ / $vmopt->{$ENV{'PBPROJ'}}/);
1016 }
1017 my $nport = $vmport->{$ENV{'PBPROJ'}};
1018 $nport = "$pbport" if (defined $pbport);
1019
1020 my $cmd;
1021 my $vmcmd; # has to be used for pb_check_ps
1022 my $vmm; # has to be used for pb_check_ps
1023 if ($vmtype eq "qemu") {
1024 my $qemucmd32;
1025 my $qemucmd64;
1026 if ($arch eq "x86_64") {
1027 $qemucmd32 = "/usr/bin/qemu-system-i386";
1028 $qemucmd64 = "/usr/bin/qemu";
1029 } else {
1030 $qemucmd32 = "/usr/bin/qemu";
1031 $qemucmd64 = "/usr/bin/qemu-system-x86_64";
1032 }
1033 if ($v =~ /x86_64/) {
1034 $vmcmd = "$qemucmd64 -no-kqemu";
1035 } else {
1036 $vmcmd = "$qemucmd32";
1037 }
1038 $vmm = "$vmpath->{$ENV{'PBPROJ'}}/$v.qemu";
1039 if ($create != 0) {
1040 $ENV{'PBVMOPT'} .= " -cdrom $iso -boot d";
1041 }
1042 $cmd = "$vmcmd $ENV{'PBVMOPT'} -redir tcp:$nport:10.0.2.15:22 $vmm"
1043 } elsif ($vmtype eq "xen") {
1044 } elsif ($vmtype eq "vmware") {
[310]1045 } else {
[320]1046 die "VM of type $vmtype not supported. Report to the dev team";
[310]1047 }
[320]1048 my ($tmpcmd,$void) = split(/ +/,$cmd);
1049 my $vmexist = pb_check_ps($tmpcmd,$vmm);
1050 my $vmpid = 0;
1051 if (! $vmexist) {
1052 if ($create != 0) {
1053 if (($vmtype eq "qemu") || ($vmtype eq "xen")) {
1054 pb_system("/usr/bin/qemu-img create -f qcow2 $vmm $vmsize->{$ENV{'PBPROJ'}}","Creating the QEMU VM");
1055 } elsif ($vmtype eq "vmware") {
1056 } else {
1057 }
1058 }
1059 if (! -f "$vmm") {
1060 pb_log(0,"Unable to find VM $vmm\n");
1061 } else {
1062 pb_system("$cmd &","Launching the VM $vmm");
1063 pb_system("sleep $vmtmout->{$ENV{'PBPROJ'}}","Waiting for VM $v to come up");
1064 $vmpid = pb_check_ps($tmpcmd,$vmm);
[357]1065 pb_log(0,"VM $vmm launched (pid $vmpid)\n");
[320]1066 }
[310]1067 } else {
[320]1068 pb_log(0,"Found an existing VM $vmm (pid $vmexist)\n");
[310]1069 }
[320]1070 return($vmexist,$vmpid);
1071 # VE here
[310]1072 } else {
[320]1073 # Get VE context
[415]1074 my ($ptr,$vetmout,$vepath,$verebuild,$veconf) = pb_conf_get("vetype","vetmout","vepath","verebuild","veconf");
[320]1075 my $vetype = $ptr->{$ENV{'PBPROJ'}};
[310]1076
[320]1077 # Get distro context
1078 my ($name,$ver,$darch) = split(/-/,$v);
1079 chomp($darch);
1080 my ($ddir, $dver, $dfam, $dtype, $pbsuf) = pb_distro_init($name,$ver);
[142]1081
[320]1082 if ($vetype eq "chroot") {
1083 # Architecture consistency
1084 if ($arch ne $darch) {
1085 die "Unable to launch a VE of architecture $darch on a $arch platform" if (not (($darch eq "x86_64") && ($arch =~ /i?86/)));
1086 }
[142]1087
[320]1088 if (($create != 0) || ($verebuild->{$ENV{'PBPROJ'}} eq "true") || ($force == 1)) {
1089 # We have to rebuild the chroot
1090 if ($dtype eq "rpm") {
1091 pb_system("sudo /usr/sbin/mock --init --resultdir=\"/tmp\" --configdir=\"$veconf->{$ENV{'PBPROJ'}}\" -r $v","Creating the mock VE");
1092 # Once setup we need to install some packages, the pb account, ...
1093 pb_system("sudo /usr/sbin/mock --install --configdir=\"$veconf->{$ENV{'PBPROJ'}}\" -r $v su","Configuring the mock VE");
1094 #pb_system("sudo /usr/sbin/mock --init --resultdir=\"/tmp\" --configdir=\"$veconf->{$ENV{'PBPROJ'}}\" --basedir=\"$vepath->{$ENV{'PBPROJ'}}\" -r $v","Creating the mock VE");
1095 } elsif ($dtype eq "deb") {
1096 pb_system("","Creating the pbuilder VE");
1097 } elsif ($dtype eq "ebuild") {
1098 die "Please teach the dev team how to build gentoo chroot";
1099 } else {
1100 die "Unknown distribution type $dtype. Report to dev team";
1101 }
[310]1102 }
[320]1103 # Nothing more to do for VE. No real launch
[274]1104 } else {
[320]1105 die "VE of type $vetype not supported. Report to the dev team";
[262]1106 }
[141]1107 }
1108}
[142]1109
[320]1110sub pb_build2v {
[118]1111
[320]1112my $vtype = shift;
[142]1113
[320]1114# Prepare the script to be executed on the VM/VE
1115# in $ENV{'PBDESTDIR'}/pbscript
[353]1116#my ($ntp) = pb_conf_get($vtype."ntp");
1117#my $vntp = $ntp->{$ENV{'PBPROJ'}};
[118]1118
[320]1119open(SCRIPT,"> $ENV{'PBDESTDIR'}/pbscript") || die "Unable to create $ENV{'PBDESTDIR'}/pbscript";
1120print SCRIPT "#!/bin/bash\n";
1121print SCRIPT "echo ... Execution needed\n";
1122print SCRIPT "# This is in directory delivery\n";
1123print SCRIPT "# Setup the variables required for building\n";
1124print SCRIPT "export PBPROJ=$ENV{'PBPROJ'}\n";
1125print SCRIPT "# Preparation for pb\n";
1126print SCRIPT "mv .pbrc \$HOME\n";
1127print SCRIPT "cd ..\n";
1128# Force new date to be in the future compared to the date of the tar file by adding 1 minute
1129my @date=pb_get_date();
1130$date[1]++;
1131my $upddate = strftime("%m%d%H%M%Y", @date);
[353]1132#print SCRIPT "echo Setting up date on $vntp...\n";
[320]1133# Or use ntpdate if available TBC
1134print SCRIPT "sudo date $upddate\n";
[353]1135# Get list of packages to build and get some ENV vars as well
1136my $ptr = pb_get_pkg();
1137@pkgs = @$ptr;
1138my $p = join(' ',@pkgs) if (@pkgs);
1139print SCRIPT "export PBPROJVER=$ENV{'PBPROJVER'}\n";
1140print SCRIPT "export PBPROJTAG=$ENV{'PBPROJTAG'}\n";
[320]1141print SCRIPT "export PBPACKAGER=\"$ENV{'PBPACKAGER'}\"\n";
1142print SCRIPT "# Build\n";
1143print SCRIPT "echo Building packages on $vtype...\n";
1144print SCRIPT "pb -p $ENV{'PBPROJ'} build2pkg $p\n";
1145close(SCRIPT);
1146chmod 0755,"$ENV{'PBDESTDIR'}/pbscript";
1147
1148my ($v,$all) = pb_get_v($vtype);
1149
1150# Send tar files when we do a global generation
1151pb_build2ssh() if ($all == 1);
1152
1153my ($vmexist,$vmpid) = (undef,undef);
1154
1155foreach my $v (@$v) {
1156 if ($vtype eq "vm") {
[142]1157 # Launch the VM
[357]1158 ($vmexist,$vmpid) = pb_launchv($vtype,$v,0);
[118]1159
[274]1160 # Skip that VM if it something went wrong
1161 next if (($vmpid == 0) && ($vmexist == 0));
[118]1162 }
[320]1163 # Gather all required files to send them to the VM/VE
[347]1164 # and launch the build through pbscript
[357]1165 pb_log(2,"Calling send2target $vtype,$v,$vmexist,$vmpid\n");
[320]1166 pb_send2target($vtype,"$v",$vmexist,$vmpid);
[105]1167}
[320]1168}
[105]1169
[262]1170
[199]1171sub pb_newver {
1172
[204]1173 die "-V Version parameter needed" if ((not defined $newver) || ($newver eq ""));
[340]1174
[366]1175 # Need this call for PBDIR
1176 my ($scheme2,$uri) = pb_cms_init($pbinit);
[361]1177
[415]1178 my ($pbconf) = pb_conf_get("pbconfurl");
[366]1179 $uri = $pbconf->{$ENV{'PBPROJ'}};
1180 my ($scheme, $account, $host, $port, $path) = pb_get_uri($uri);
1181
[361]1182 # Checking CMS repositories status
[358]1183 my ($pburl) = pb_conf_get("pburl");
[366]1184 ($scheme2, $account, $host, $port, $path) = pb_get_uri($pburl->{$ENV{'PBPROJ'}});
[340]1185
1186 if ($scheme !~ /^svn/) {
[199]1187 die "Only SVN is supported at the moment";
1188 }
[358]1189 my $res = pb_cms_isdiff($scheme,$ENV{'PBROOTDIR'});
[361]1190 die "ERROR: No differences accepted in CMS for $ENV{'PBROOTDIR'} before creating a new version" if ($res != 0);
[358]1191
1192 $res = pb_cms_isdiff($scheme2,$ENV{'PBDIR'});
[361]1193 die "ERROR: No differences accepted in CMS for $ENV{'PBDIR'} before creating a new version" if ($res != 0);
[358]1194
1195 # Tree identical between PBCONFDIR and PBROOTDIR. The delta is what
1196 # we want to get for the root of the new URL
1197
1198 my $tmp = $ENV{'PBROOTDIR'};
1199 $tmp =~ s|^$ENV{'PBCONFDIR'}||;
1200
1201 my $newurl = "$uri/".dirname($tmp)."/$newver";
[366]1202 # Should probably use projver in the old file
1203 my $oldver= basename($tmp);
[361]1204
1205 # Checking pbcl files
[366]1206 foreach my $f (<$ENV{'PBROOTDIR'}/*/pbcl>) {
[361]1207 open(PBCL,$f) || die "Unable to open $f";
1208 my $foundnew = 0;
1209 while (<PBCL>) {
[363]1210 $foundnew = 1 if (/^$newver \(/);
[361]1211 }
1212 close(PBCL);
[362]1213 die "ERROR: version $newver not found in $f" if ($foundnew == 0);
[361]1214 }
1215
[366]1216 # Duplicate and extract project-builder part
[361]1217 pb_log(2,"Copying $uri/$tmp to $newurl\n");
[366]1218 pb_cms_copy($scheme,"$uri/$tmp",$newurl);
1219 pb_log(2,"Checkout $newurl to $ENV{'PBROOTDIR'}/../$newver\n");
[383]1220 pb_cms_up($scheme,"$ENV{'PBCONFDIR'}/..");
[361]1221
[366]1222 # Duplicate and extract project
1223 my $newurl2 = "$pburl->{$ENV{'PBPROJ'}}/".dirname($tmp)."/$newver";
1224
1225 pb_log(2,"Copying $pburl->{$ENV{'PBPROJ'}}/$tmp to $newurl2\n");
1226 pb_cms_copy($scheme,"$pburl->{$ENV{'PBPROJ'}}/$tmp",$newurl2);
1227 pb_log(2,"Checkout $newurl2 to $ENV{'PBDIR'}/../$newver\n");
[383]1228 pb_cms_up($scheme,"$ENV{'PBDIR'}/..");
[366]1229
[361]1230 # Update the .pb file
[358]1231 open(FILE,"$ENV{'PBROOTDIR'}/../$newver/$ENV{'PBPROJ'}.pb") || die "Unable to open $ENV{'PBROOTDIR'}/../$newver/$ENV{'PBPROJ'}.pb";
1232 open(OUT,"> $ENV{'PBROOTDIR'}/../$newver/$ENV{'PBPROJ'}.pb.new") || die "Unable to write to $ENV{'PBROOTDIR'}/../$newver/$ENV{'PBPROJ'}.pb.new";
[208]1233 while(<FILE>) {
[361]1234 s/^projver\s+$ENV{'PBPROJ'}\s*=\s*$oldver/projver $ENV{'PBPROJ'} = $newver/;
1235 pb_log(0,"Changing projver from $oldver to $newver in $ENV{'PBROOTDIR'}/../$newver/$ENV{'PBPROJ'}.pb\n") if (/^projver\s+$ENV{'PBPROJ'}\s*=\s*$oldver/);
1236 s/^testver/#testver/;
1237 pb_log(0,"Commenting testver in $ENV{'PBROOTDIR'}/../$newver/$ENV{'PBPROJ'}.pb\n") if (/^testver/);
[211]1238 print OUT $_;
[208]1239 }
1240 close(FILE);
[211]1241 close(OUT);
[358]1242 rename("$ENV{'PBROOTDIR'}/../$newver/$ENV{'PBPROJ'}.pb.new","$ENV{'PBROOTDIR'}/../$newver/$ENV{'PBPROJ'}.pb");
[363]1243
[358]1244 pb_log(2,"Checkin $ENV{'PBROOTDIR'}/../$newver\n");
[363]1245 pb_cms_checkin($scheme,"$ENV{'PBROOTDIR'}/../$newver");
[199]1246}
1247
[293]1248#
[320]1249# Return the list of VMs/VEs we are working on
[105]1250# $all is a flag to know if we return all of them
1251# or only some (if all we publish also tar files in addition to pkgs
1252#
[320]1253sub pb_get_v {
[91]1254
[320]1255my $vtype = shift;
1256my @v;
[105]1257my $all = 0;
[320]1258my $vlist;
1259my $pbv = 'PBV';
[91]1260
[320]1261if ($vtype eq "vm") {
1262 $vlist = "vmlist";
1263} elsif ($vtype eq "ve") {
1264 $vlist = "velist";
1265}
1266# Get VM/VE list
1267if ((not defined $ENV{$pbv}) || ($ENV{$pbv} =~ /^all$/)) {
1268 my ($ptr) = pb_conf_get($vlist);
1269 $ENV{$pbv} = $ptr->{$ENV{'PBPROJ'}};
[105]1270 $all = 1;
[91]1271}
[320]1272pb_log(2,"$vtype: $ENV{$pbv}\n");
1273@v = split(/,/,$ENV{$pbv});
1274return(\@v,$all);
[91]1275}
1276
[320]1277# Function to create a potentialy missing pb account on the VM/VE, and adds it to sudo
1278# Needs to use root account to connect to the VM/VE
1279# pb will take your local public SSH key to access
[346]1280# the pb account in the VM later on if needed
1281sub pb_setup_v {
[320]1282
1283my $vtype = shift;
1284
[353]1285my ($vm,$all) = pb_get_v($vtype);
1286
[346]1287# Script generated
1288my $pbscript = "$ENV{'PBDESTDIR'}/setupv";
[320]1289
[353]1290foreach my $v (@$vm) {
1291 # Name of the account to deal with for VM/VE
1292 # Do not use the one passed potentially with -a
1293 my ($pbac) = pb_conf_get($vtype."login");
[354]1294 my ($key,$zero0,$zero1,$zero2);
[357]1295 my ($vmexist,$vmpid);
[346]1296
[353]1297 if ($vtype eq "vm") {
1298 # Prepare the key to be used and transfered remotely
1299 my $keyfile = pb_ssh_get(1);
1300
1301 my ($vmhost,$vmport) = pb_conf_get("vmhost","vmport");
1302 my $nport = $vmport->{$ENV{'PBPROJ'}};
1303 $nport = "$pbport" if (defined $pbport);
[347]1304
[353]1305 # Launch the VM
[357]1306 ($vmexist,$vmpid) = pb_launchv($vtype,$v,0);
[347]1307
[353]1308 # Skip that VM if something went wrong
1309 return if (($vmpid == 0) && ($vmexist == 0));
1310
[354]1311 # Store the pub key part in a variable
1312 open(FILE,"$keyfile.pub") || die "Unable to open $keyfile.pub";
1313 ($zero0,$zero1,$zero2) = split(/ /,<FILE>);
1314 close(FILE);
1315
1316 $key = "\Q$zero1";
1317
[353]1318 pb_system("cat $keyfile.pub | ssh -q -p $nport -i $keyfile root\@$vmhost->{$ENV{'PBPROJ'}} \"mkdir -p .ssh ; chmod 700 .ssh ; cat >> .ssh/authorized_keys ; chmod 600 .ssh/authorized_keys\"","Copying local keys to $vtype. This will require the root password");
1319 # once this is done, we can do what we want on the VM remotely
1320 }
1321
1322 # Prepare the script to be executed on the VM/VE
1323 # in $ENV{'PBDESTDIR'}/setupv
1324
1325 open(SCRIPT,"> $pbscript") || die "Unable to create $pbscript";
1326 print SCRIPT << 'EOF';
[320]1327#!/usr/bin/perl -w
1328
[346]1329use strict;
1330use File::Copy;
1331
[354]1332EOF
1333 if ($vtype eq "vm") {
1334 print SCRIPT << 'EOF';
1335# Removes duplicate in .ssh/authorized_keys of our key if needed
1336#
1337my $file1="$ENV{'HOME'}/.ssh/authorized_keys";
1338open(PBFILE,$file1) || die "Unable to open $file1";
1339open(PBOUT,"> $file1.new") || die "Unable to open $file1.new";
1340my $count = 0;
1341while (<PBFILE>) {
1342EOF
1343 print SCRIPT << "EOF";
1344 if (/ $key /) {
1345 \$count++;
1346 }
1347print PBOUT \$_ if ((\$count <= 1) || (\$_ !~ / $key /));
1348}
1349close(PBFILE);
1350close(PBOUT);
1351rename("\$file1.new",\$file1);
1352chmod 0600,\$file1;
1353EOF
1354 }
1355 print SCRIPT << 'EOF';
1356
1357# Adds $pbac->{$ENV{'PBPROJ'}} as an account if needed
1358#
[346]1359my $file="/etc/passwd";
[320]1360open(PBFILE,$file) || die "Unable to open $file";
1361my $found = 0;
1362while (<PBFILE>) {
[346]1363EOF
[353]1364 print SCRIPT << "EOF";
1365 \$found = 1 if (/^$pbac->{$ENV{'PBPROJ'}}:/);
[346]1366EOF
[353]1367 print SCRIPT << 'EOF';
[320]1368}
1369close(PBFILE);
1370
1371if ( $found == 0 ) {
1372 if ( ! -d "/home" ) {
1373 mkdir "/home";
1374 }
[346]1375EOF
[353]1376 print SCRIPT << "EOF";
1377system "groupadd $pbac->{$ENV{'PBPROJ'}}";
1378system "useradd $pbac->{$ENV{'PBPROJ'}} -g $pbac->{$ENV{'PBPROJ'}} -m -d /home/$pbac->{$ENV{'PBPROJ'}}";
[320]1379
[354]1380# allow ssh entry to build
1381#
[353]1382chdir "/home/$pbac->{$ENV{'PBPROJ'}}";
[320]1383mkdir ".ssh",0700;
[347]1384# Allow those accessing root to access the build account
[348]1385copy("\$ENV{'HOME'}/.ssh/authorized_keys",".ssh/authorized_keys");
[320]1386chmod 0600,".ssh/authorized_keys";
[353]1387system 'chown -R $pbac->{$ENV{'PBPROJ'}}:$pbac->{$ENV{'PBPROJ'}} .ssh';
[320]1388
[346]1389EOF
[353]1390 print SCRIPT << 'EOF';
[346]1391}
1392
[347]1393# No passwd for build account only keys
[320]1394$file="/etc/shadow";
1395open(PBFILE,$file) || die "Unable to open $file";
1396open(PBOUT,"> $file.new") || die "Unable to open $file.new";
1397while (<PBFILE>) {
[346]1398EOF
[353]1399 print SCRIPT << "EOF";
1400 s/^$pbac->{$ENV{'PBPROJ'}}:\!\!:/$pbac->{$ENV{'PBPROJ'}}:*:/;
1401 s/^$pbac->{$ENV{'PBPROJ'}}:\!:/$pbac->{$ENV{'PBPROJ'}}:*:/; #SLES 9 e.g.
[346]1402EOF
[353]1403 print SCRIPT << 'EOF';
[320]1404 print PBOUT $_;
1405}
1406close(PBFILE);
1407close(PBOUT);
1408rename("$file.new",$file);
1409chmod 0640,$file;
1410
1411# pb has to be added to portage group on gentoo
1412
[346]1413# Adapt sudoers
1414$file="/etc/sudoers";
1415open(PBFILE,$file) || die "Unable to open $file";
1416open(PBOUT,"> $file.new") || die "Unable to open $file.new";
1417while (<PBFILE>) {
1418EOF
[353]1419 print SCRIPT << "EOF";
1420 next if (/^$pbac->{$ENV{'PBPROJ'}} /);
[346]1421EOF
[353]1422 print SCRIPT << 'EOF';
[346]1423 s/Defaults[ \t]+requiretty//;
1424 print PBOUT $_;
1425}
1426close(PBFILE);
1427EOF
[353]1428 print SCRIPT << "EOF";
1429# This is needed in order to be able to halt the machine from the $pbac->{$ENV{'PBPROJ'}} account at least
1430print PBOUT "$pbac->{$ENV{'PBPROJ'}} ALL=(ALL) NOPASSWD:ALL\n";
[346]1431EOF
[353]1432 print SCRIPT << 'EOF';
[346]1433close(PBOUT);
1434rename("$file.new",$file);
1435chmod 0440,$file;
1436
1437EOF
[353]1438
1439 my $SCRIPT = \*SCRIPT;
1440
1441 pb_install_deps($SCRIPT);
1442
1443 print SCRIPT << 'EOF';
[346]1444# Suse wants sudoers as 640
1445if (($ddir eq "sles") || (($ddir eq "suse")) && ($dver ne "10.3")) {
1446 chmod 0640,$file;
1447}
1448
1449# Sync date
[353]1450#system "/usr/sbin/ntpdate ntp.pool.org";
[346]1451
[352]1452system "rm -rf project-builder-* ; wget --passive-ftp ftp://ftp.mondorescue.org/src/project-builder-latest.tar.gz ; tar xvfz project-builder-latest.tar.gz ; cd project-builder-* ; perl Makefile.PL ; make ; make install ; cd .. ; rm -rf project-builder-*";
[358]1453system "pb 2>&1 | head -5";
[357]1454EOF
1455 if ((! $vmexist) && ($vtype eq "vm")) {
1456 print SCRIPT << 'EOF';
[356]1457system "sudo /sbin/halt -p";
[346]1458EOF
[357]1459 }
[353]1460
1461 # Adds pb_distro_init from ProjectBuilder::Distribution
1462 foreach my $d (@INC) {
[405]1463 my @f = ("$d/ProjectBuilder/Base.pm","$d/ProjectBuilder/Distribution.pm");
1464 foreach my $f (@f) {
1465 if (-f "$f") {
1466 open(PBD,"$f") || die "Unable to open $f";
1467 while (<PBD>) {
1468 next if (/^package/);
1469 next if (/^use Exporter/);
1470 next if (/^use ProjectBuilder::Base/);
1471 next if (/^our \@/);
1472 print SCRIPT $_;
1473 }
1474 close(PBD);
[353]1475 }
[347]1476 }
1477 }
[353]1478 close(SCRIPT);
1479 chmod 0755,"$pbscript";
1480
1481 # That build script needs to be run as root
1482 $pbaccount = "root";
1483 pb_script2v($pbscript,$vtype);
[347]1484}
[353]1485return;
[346]1486}
1487
[347]1488sub pb_install_deps {
[346]1489
[348]1490my $SCRIPT = shift;
[346]1491
[348]1492print {$SCRIPT} << 'EOF';
[346]1493# We need to have that pb_distro_init function
[347]1494# Get it from Project-Builder::Distribution
[320]1495my ($ddir, $dver, $dfam, $dtype, $pbsuf) = pb_distro_init();
1496print "distro tuple: ".join(',',($ddir, $dver, $dfam, $dtype, $pbsuf))."\n";
1497
1498# Get and install pb
[357]1499my $insdm = "rm -rf Date-Manip* ; wget http://search.cpan.org/CPAN/authors/id/S/SB/SBECK/Date-Manip-5.48.tar.gz ; tar xvfz Date-Manip-5.48.tar.gz ; cd Date-Manip* ; perl Makefile.PL ; make ; make install ; cd .. ; rm -rf Date-Manip*";
1500my $insmb = "rm -rf Module-Build* ; wget http://search.cpan.org/CPAN/authors/id/K/KW/KWILLIAMS/Module-Build-0.2808.tar.gz ; tar xvfz Module-Build-0.2808.tar.gz ; cd Module-Build* ; perl Makefile.PL ; make ; make install ; cd .. ; rm -rf Module-Build*";
1501my $insfm = "rm -rf File-MimeInfo* ; wget http://search.cpan.org/CPAN/authors/id/P/PA/PARDUS/File-MimeInfo/File-MimeInfo-0.15.tar.gz ; tar xvfz File-MimeInfo-0.15.tar.gz ; cd File-MimeInfo* ; perl Makefile.PL ; make ; make install ; cd .. ; rm -rf File-MimeInfo*";
1502my $insfb = "rm -rf File-Basedir* ; wget http://search.cpan.org/CPAN/authors/id/P/PA/PARDUS/File-BaseDir-0.03.tar.gz ; tar xvfz File-BaseDir-0.03.tar.gz ; cd File-BaseDir* ; perl Makefile.PL ; make ; make install ; cd .. ; rm -rf File-BaseDir*";
1503
[320]1504if ( $ddir eq "fedora" ) {
1505 system "yum clean all";
[346]1506 #system "yum update -y";
[320]1507 my $arch=`uname -m`;
1508 my $opt = "";
1509 chomp($arch);
1510 if ($arch eq "x86_64") {
1511 $opt="--exclude=*.i?86";
1512 }
1513
[353]1514 system "yum -y $opt install rpm-build wget patch ntp sudo perl-DateManip perl-File-MimeInfo perl-ExtUtils-MakeMaker";
[357]1515 if ($dver eq 4) {
1516 system "$insmb";
1517 system "$insfm";
1518 system "$insfb";
1519 }
1520} elsif (( $dfam eq "rh" ) || ($ddir eq "sles") || (($ddir eq "suse") && (($dver eq "10.1") || ($dver eq "10.0"))) || ($ddir eq "slackware")) {
[358]1521 # Suppose pkg are installed already as no online mirror available
[320]1522 system "rpm -e lsb 2>&1 > /dev/null";
[357]1523 system "$insdm";
[358]1524 system "$insmb";
1525 system "$insfm";
1526 system "$insfb";
[320]1527} elsif ($ddir eq "suse") {
1528 # New OpenSuSE
[358]1529 system "$insmb";
1530 system "$insfm";
1531 system "$insfb";
[320]1532 system "export TERM=linux ; liste=\"\" ; for i in make wget patch sudo perl-DateManip perl-File-HomeDir xntp; do rpm -q \$i 1> /dev/null 2> /dev/null ; if [ \$\? != 0 ]; then liste=\"\$liste \$i\"; fi; done; echo \"Liste: \$liste\" ; if [ \"\$liste\" != \"\" ]; then yast2 -i \$liste ; fi";
1533} elsif ( $dfam eq "md" ) {
[357]1534 system "urpmi.update -a ; urpmi --auto rpm-build wget sudo patch ntp-client perl-File-MimeInfo";
1535 if (($ddir eq "mandrake") && ($dver eq "10.1")) {
1536 system "$insdm";
1537 } else {
1538 system "urpmi --auto perl-DateManip";
1539 }
[320]1540} elsif ( $dfam eq "du" ) {
1541 if (( $dver eq "3.1" ) && ($ddir eq "debian")) {
[346]1542 #system "apt-get update";
[358]1543 system "$insfb";
1544 system "$insfm";
1545 system "apt-get -y install wget patch ssh sudo debian-builder dh-make fakeroot ntpdate libmodule-build-perl libdate-manip-perl";
[320]1546 } else {
[358]1547 system "apt-get update; apt-get -y install wget patch openssh-server dpkg-dev sudo debian-builder dh-make fakeroot ntpdate libfile-mimeinfo-perl libmodule-build-perl libdate-manip-perl";
[320]1548 }
1549} elsif ( $dfam eq "gen" ) {
[358]1550 #system "emerge -u system ; emerge wget sudo ntp DateManip File-MimeInfo";
1551 system "emerge wget sudo ntp DateManip File-MimeInfo";
[320]1552} else {
1553 print "No pkg to install\n";
1554}
1555EOF
1556}
1557
[347]1558# Return the SSH key file to use
1559# Potentially create it if needed
1560
1561sub pb_ssh_get {
1562
1563my $create = shift || 0; # Do not create keys by default
1564
1565# Check the SSH environment
1566my $keyfile = undef;
1567
1568# We have specific keys by default
1569$keyfile = "$ENV{'HOME'}/.ssh/pb_dsa";
[348]1570if (!(-e $keyfile) && ($create eq 1)) {
[347]1571 pb_system("ssh-keygen -q -b 1024 -N '' -f $keyfile -t dsa","Generating SSH keys for pb");
1572}
1573
1574$keyfile = "$ENV{'HOME'}/.ssh/id_rsa" if (-s "$ENV{'HOME'}/.ssh/id_rsa");
1575$keyfile = "$ENV{'HOME'}/.ssh/id_dsa" if (-s "$ENV{'HOME'}/.ssh/id_dsa");
1576$keyfile = "$ENV{'HOME'}/.ssh/pb_dsa" if (-s "$ENV{'HOME'}/.ssh/pb_dsa");
1577die "Unable to find your public ssh key under $keyfile" if (not defined $keyfile);
1578return($keyfile);
1579}
1580
1581
[145]1582# Returns the pid of a running VM command using a specific VM file
[142]1583sub pb_check_ps {
1584 my $vmcmd = shift;
1585 my $vmm = shift;
1586 my $vmexist = 0; # FALSE by default
1587
1588 open(PS, "ps auxhww|") || die "Unable to call ps";
1589 while (<PS>) {
1590 next if (! /$vmcmd/);
1591 next if (! /$vmm/);
1592 my ($void1, $void2);
1593 ($void1, $vmexist, $void2) = split(/ +/);
1594 last;
1595 }
1596 return($vmexist);
1597}
1598
1599
[77]1600sub pb_extract_build_files {
[25]1601
1602my $src=shift;
1603my $dir=shift;
[26]1604my $ddir=shift;
[28]1605my @files;
[25]1606
[188]1607if ($src =~ /tar\.gz$/) {
1608 pb_system("tar xfpz $src $dir","Extracting build files");
1609} elsif ($src =~ /tar\.bz2$/) {
1610 pb_system("tar xfpj $src $dir","Extracting build files");
1611} else {
1612 die "Unknown compression algorithm for $src";
1613}
[25]1614opendir(DIR,"$dir") || die "Unable to open directory $dir";
1615foreach my $f (readdir(DIR)) {
1616 next if ($f =~ /^\./);
[26]1617 move("$dir/$f","$ddir") || die "Unable to move $dir/$f to $ddir";
[315]1618 pb_log(2,"mv $dir/$f $ddir\n");
[28]1619 push @files,"$ddir/$f";
[25]1620}
1621closedir(DIR);
[26]1622# Not enough but still a first cleanup
[74]1623pb_rm_rf("$dir");
[28]1624return(@files);
[25]1625}
1626
[315]1627sub pb_list_bfiles {
1628
1629my $dir = shift;
1630my $pbpkg = shift;
1631my $bfiles = shift;
1632my $pkgfiles = shift;
1633my $supfiles = shift;
1634
1635opendir(BDIR,"$dir") || die "Unable to open dir $dir: $!";
1636foreach my $f (readdir(BDIR)) {
1637 next if ($f =~ /^\./);
1638 $bfiles->{$f} = "$dir/$f";
[340]1639 $bfiles->{$f} =~ s~$ENV{'PBROOTDIR'}~~;
[315]1640 if (defined $supfiles->{$pbpkg}) {
1641 $pkgfiles->{$f} = "$dir/$f" if ($f =~ /$supfiles->{$pbpkg}/);
1642 }
1643}
1644closedir(BDIR);
1645}
1646
[395]1647
1648#
1649# Return the list of packages we are working on in a non CMS action
1650#
1651sub pb_get_pkg {
1652
1653my @pkgs = ();
1654
1655my ($var) = pb_conf_read("$ENV{'PBDESTDIR'}/$ENV{'PBPROJVER'}-$ENV{'PBPROJTAG'}.pb","pbpkg");
1656@pkgs = keys %$var;
1657
1658pb_log(0,"Packages: ".join(',',@pkgs)."\n");
1659return(\@pkgs);
1660}
1661
16621;
Note: See TracBrowser for help on using the repository browser.